package com.trailer.base.binding;

import android.graphics.Canvas;

import com.chad.library.adapter.base.BaseQuickAdapter;
import com.chad.library.adapter.base.listener.OnItemClickListener;
import com.chad.library.adapter.base.listener.OnItemDragListener;
import com.chad.library.adapter.base.listener.OnItemSwipeListener;
import com.socks.library.KLog;
import com.trailer.base.R;
import com.trailer.base.callback.OnAdapterDataSizeChangedListener;
import com.trailer.base.callback.OnAdapterItemInsertedListener;
import com.trailer.base.callback.OnRecyclerViewItemDragedEndListener;
import com.trailer.base.callback.OnRecyclerViewItemSwipeEndListener;
import com.trailer.base.callback.OnReyclerViewScrollListener;
import com.trailer.base.callback.OnReyclerViewScrollStateChangeListener;

import java.util.List;

import androidx.annotation.NonNull;
import androidx.databinding.BindingAdapter;
import androidx.databinding.adapters.ListenerUtil;
import androidx.recyclerview.widget.RecyclerView;

public class RecyclerViewBindingAdapter {


    @BindingAdapter("on_item_click")
    public static void setOnItemClickListener(RecyclerView view, OnItemClickListener onItemClickListener) {

        RecyclerView.Adapter adapter = view.getAdapter();
        if (adapter instanceof BaseQuickAdapter) {
            BaseQuickAdapter quickAdapter = (BaseQuickAdapter) adapter;
            quickAdapter.setOnItemClickListener(onItemClickListener);
        }

    }

    @BindingAdapter("animator_change_duration")
    public static void setAnimatorChangeDuration(RecyclerView view, long duration) {
        RecyclerView.ItemAnimator itemAnimator = view.getItemAnimator();
        if (itemAnimator != null) {
            itemAnimator.setChangeDuration(duration);
        }
    }

    @BindingAdapter(value = {"list_data", "page"}, requireAll = false)
    public static <T> void listData(RecyclerView view, List<T> data, int page) {
        if (data == null) {
            return;
        }

        RecyclerView.Adapter adapter = view.getAdapter();

        if (adapter instanceof BaseQuickAdapter) {
            BaseQuickAdapter quickAdapter = (BaseQuickAdapter) adapter;
            if (page <= 1) {
                quickAdapter.setList(data);
            } else {
                quickAdapter.addData(data);
            }
        }
    }

    @BindingAdapter(value = {"adapter", "on_data_size_changed", "on_item_inserted", "on_drag", "on_swipe", "on_drag_end", "on_swipe_end"}, requireAll = false)
    public static <
            I extends OnAdapterItemInsertedListener,
            T extends OnAdapterDataSizeChangedListener,
            H extends OnItemDragListener,
            D extends OnItemSwipeListener,
            A extends OnRecyclerViewItemDragedEndListener,
            B extends OnRecyclerViewItemSwipeEndListener
            > void setAdapter(
            RecyclerView view,
            BaseQuickAdapter adapter,
            T listener,
            I insertListener,
            H dragListener,
            D swipeListener,
            A dragEndListener,
            B swipeEndListener
    ) {
        if (adapter == null) {
            return;
        }

        KLog.d();
        view.setAdapter(adapter);

        onDataSizeChanged(adapter, listener, insertListener);
        setDraggableListener(view, dragListener, swipeListener, dragEndListener, swipeEndListener);
    }


    public static <T extends OnItemDragListener, D extends OnItemSwipeListener, A extends OnRecyclerViewItemDragedEndListener, B extends OnRecyclerViewItemSwipeEndListener> void setDraggableListener(RecyclerView view, T dragListener, D swipeListener, A dragEndListener, B swipeEndListener) {

        RecyclerView.Adapter adapter = view.getAdapter();

        if (adapter instanceof BaseQuickAdapter) {
            BaseQuickAdapter quickAdapter = (BaseQuickAdapter) adapter;

            if (dragListener != null) {
                quickAdapter.getDraggableModule().setOnItemDragListener(dragListener);
            } else {
                if (dragEndListener != null) {

                    quickAdapter.getDraggableModule().setOnItemDragListener(new OnItemDragListener() {
                        @Override
                        public void onItemDragStart(RecyclerView.ViewHolder viewHolder, int pos) {

                        }

                        @Override
                        public void onItemDragMoving(RecyclerView.ViewHolder source, int from, RecyclerView.ViewHolder target, int to) {

                        }

                        @Override
                        public void onItemDragEnd(RecyclerView.ViewHolder viewHolder, int pos) {
                            dragEndListener.onItemDragEnd(viewHolder, pos);
                        }
                    });
                }
            }

            if (swipeListener != null) {
                quickAdapter.getDraggableModule().setOnItemSwipeListener(swipeListener);
            } else {
                if (swipeEndListener != null) {
                    quickAdapter.getDraggableModule().setOnItemSwipeListener(new OnItemSwipeListener() {
                        @Override
                        public void onItemSwipeStart(RecyclerView.ViewHolder viewHolder, int pos) {

                        }

                        @Override
                        public void clearView(RecyclerView.ViewHolder viewHolder, int pos) {

                        }

                        @Override
                        public void onItemSwiped(RecyclerView.ViewHolder viewHolder, int pos) {
                            swipeEndListener.onItemSwipeEnd(viewHolder, pos);
                        }

                        @Override
                        public void onItemSwipeMoving(Canvas canvas, RecyclerView.ViewHolder viewHolder, float dX, float dY, boolean isCurrentlyActive) {

                        }
                    });
                }
            }

        }
    }


    @BindingAdapter(value = {"on_scroll", "on_scroll_state_changed"}, requireAll = false)
    public static <T extends OnReyclerViewScrollListener, D extends OnReyclerViewScrollStateChangeListener> void setAdapter(RecyclerView view, T listener, D stateListener) {
        RecyclerView.OnScrollListener newListener;
        if (listener == null && stateListener == null) {
            newListener = null;
        } else {

            newListener = new RecyclerView.OnScrollListener() {
                @Override
                public void onScrollStateChanged(@NonNull RecyclerView recyclerView, int newState) {
                    super.onScrollStateChanged(recyclerView, newState);
                    if (stateListener != null) {
                        stateListener.onScrollStateChanged(recyclerView, newState);
                    }
                }

                @Override
                public void onScrolled(@NonNull RecyclerView recyclerView, int dx, int dy) {
                    super.onScrolled(recyclerView, dx, dy);
                    if (listener != null) {
                        listener.onScrolled(recyclerView, dx, dy);
                    }
                }
            };
        }

        RecyclerView.OnScrollListener oldListener = ListenerUtil.trackListener(view, newListener, R.id.onRecyclerViewScrollListener);

        if (oldListener != null) {
            view.removeOnScrollListener(oldListener);
        }

        if (newListener != null) {
            view.addOnScrollListener(newListener);
        }
    }

    @BindingAdapter("list_item")
    public static <T> void listItem(RecyclerView view, T item) {
        if (item == null) {
            return;
        }
        RecyclerView.Adapter adapter = view.getAdapter();
        if (adapter instanceof BaseQuickAdapter) {
            ((BaseQuickAdapter) adapter).addData(item);
        }
    }

    public static <I extends OnAdapterItemInsertedListener, T extends OnAdapterDataSizeChangedListener> void onDataSizeChanged(BaseQuickAdapter adapter, T listener, I insertListener) {
        if (listener == null && insertListener == null) {
            return;
        }

        adapter.registerAdapterDataObserver(new RecyclerView.AdapterDataObserver() {

            @Override
            public void onItemRangeInserted(int positionStart, int itemCount) {
                super.onItemRangeInserted(positionStart, itemCount);
                if (listener != null) {
                    listener.onSizeChanged(adapter.getItemCount());
                }

                if (insertListener != null) {
                    insertListener.onInserted(itemCount);
                }
            }

            @Override
            public void onItemRangeRemoved(int positionStart, int itemCount) {
                super.onItemRangeRemoved(positionStart, itemCount);

                if (listener != null) {
                    listener.onSizeChanged(adapter.getItemCount());
                }
            }
        });
    }

    public static <T extends OnAdapterDataSizeChangedListener> void onItemInserted(BaseQuickAdapter adapter, T listener) {
        if (listener == null) {
            return;
        }

        adapter.registerAdapterDataObserver(new RecyclerView.AdapterDataObserver() {
            @Override
            public void onItemRangeInserted(int positionStart, int itemCount) {
                super.onItemRangeInserted(positionStart, itemCount);
                listener.onSizeChanged(itemCount);
            }
        });
    }

}
